package com.yoke.database;
/**
 * Created by jiangzeyin on 2017/1/6.
 */

import com.yoke.system.log.SystemLog;
import org.springframework.util.Assert;

import javax.sql.DataSource;
import java.sql.Connection;
import java.sql.SQLException;
import java.util.Map;
import java.util.Random;

/**
 * @author jiangzeyin
 * @create 2017 01 06 17:01
 */
public class DatabaseContextHolder {
    private static final ThreadLocal<String> threadLocal = new ThreadLocal<>();
    private static Map[] MAPS;
    private static DatabaseOptType databaseOptType = DatabaseOptType.One;
    private static Random random = new Random();

    public enum DatabaseOptType {
        One, Two, More
    }

    public DatabaseContextHolder(Map[] maps) {
        Assert.notNull(maps);
        if (maps.length == 0)
            throw new IllegalArgumentException("数据库连接信息不能为空");
        MAPS = maps;
        if (maps.length == 1)
            databaseOptType = DatabaseOptType.One;
        else if (maps.length == 2)
            databaseOptType = DatabaseOptType.Two;
        else
            databaseOptType = DatabaseOptType.More;
        SystemLog.LOG().info(" 数据库操作：" + databaseOptType.toString());
    }

    public DatabaseContextHolder() {

    }

    public static void setThreadLocal(String tag) {
        threadLocal.set(tag);
    }

    private static Map<Object, Object> targetDataSourcesMap;

    public void setTargetDataSources(Map<Object, Object> targetDataSources) {
        //super.setTargetDataSources(targetDataSources);
        DatabaseContextHolder.targetDataSourcesMap = targetDataSources;
    }


    private static Map<Object, Object> randMap() {
        return MAPS[random.nextInt(MAPS.length)];
    }

    public static DataSource getReadDataSource(String tag) {
        DataSource dataSource = null;
        if (databaseOptType == DatabaseOptType.One)
            dataSource = (DataSource) targetDataSourcesMap.get(tag);
        else if (databaseOptType == DatabaseOptType.Two)
            dataSource = (DataSource) MAPS[1].get(tag);
        else if (databaseOptType == DatabaseOptType.More)
            dataSource = (DataSource) randMap().get(tag);
        Assert.notNull(dataSource, "没有找到对应数据源：" + tag);
        return dataSource;
    }

    public static DataSource getDataSource() {
        return getReadDataSource("core");
    }


    public static DataSource getWriteDataSource(String tag) {
        DataSource dataSource = null;
        if (databaseOptType == DatabaseOptType.One)
            dataSource = (DataSource) targetDataSourcesMap.get(tag);
        else if (databaseOptType == DatabaseOptType.Two)
            dataSource = (DataSource) targetDataSourcesMap.get(tag);
        else if (databaseOptType == DatabaseOptType.More)
            dataSource = (DataSource) randMap().get(tag);
        Assert.notNull(dataSource, "没有找到对应数据源：" + tag);
        return dataSource;
    }

    public static Connection getReadConnection(String tag) throws SQLException {
        return getReadDataSource(tag).getConnection();
    }

    public static Connection getWriteConnection(String tag) throws SQLException {
        return getWriteDataSource(tag).getConnection();
    }
}
